# -*- coding: UTF-8 -*-
"""
@Project ：swift-forge-engine 
@File    ：response_schema
@IDE     ：PyCharm 
@Author  ：Tony
@Date    ：2025/2/19 11:07 
@Des     ：
"""
from datetime import datetime
from typing import Any, Generic

from fastapi import Response
from pydantic import BaseModel, ConfigDict

from APP.common.pagination import SchemaT
from APP.common.respones.response_code import CustomResponseCode, CustomResponse
from APP.config.conf import settings
from APP.utils.serializers import MsgSpecJSONResponse

_ExcludeData = set[int | str] | dict[int | str, Any]

__all__ = ['ResponseModel', 'ResponseSchemaModel', 'response_base']


class ResponseModel(BaseModel):
    """
    统一返回模型

    """

    model_config = ConfigDict(json_encoders={datetime: lambda x: x.strftime(settings.DATETIME_FORMAT)})

    code: int = CustomResponseCode.HTTP_200.code
    message: str = CustomResponseCode.HTTP_200.message
    data: Any | None = None

class ResponseSchemaModel(ResponseModel, Generic[SchemaT]):
    """
    包含 data schema 的统一返回模型，适用于非分页接口
    """

    data: SchemaT


class ResponseBase:
    """
    统一返回方法

    """

    @staticmethod
    def __response(*, res: CustomResponseCode | CustomResponse = None, data: Any | None = None) -> ResponseModel | ResponseSchemaModel:
        """
        请求成功返回通用方法

        :param res: 返回信息
        :param data: 返回数据
        :return:
        """
        return ResponseModel(code=res.code, message=res.message, data=data)

    def success(
        self,
        *,
        res: CustomResponseCode | CustomResponse = CustomResponseCode.HTTP_200,
        data: Any | None = None,
    ) -> ResponseModel | ResponseSchemaModel:
        return self.__response(res=res, data=data)

    def fail(
        self,
        *,
        res: CustomResponseCode | CustomResponse = CustomResponseCode.HTTP_400,
        data: Any = None,
    ) -> ResponseModel | ResponseSchemaModel:
        return self.__response(res=res, data=data)

    @staticmethod
    def fast_success(
        *,
        res: CustomResponseCode | CustomResponse = CustomResponseCode.HTTP_200,
        data: Any | None = None,
    ) -> Response:
        """
        此方法是为了提高接口响应速度而创建的，如果返回数据无需进行 pydantic 解析和验证，则推荐使用，相反，请不要使用！

        .. warning::

            使用此返回方法时，不要指定接口参数 response_model，也不要在接口函数后添加箭头返回类型

        :param res:
        :param data:
        :return:
        """
        return MsgSpecJSONResponse({'code': res.code, 'message': res.message, 'data': data})


response_base: ResponseBase = ResponseBase()